//
//  CTVRateMediaController.m
//  Channltv
//
//  Created by Bruno Keymolen on 19/09/07.
//  Copyright 2007 channl.tv. All rights reserved.
//

#import "CTVRateMediaController.h"
#import "CTVCache.h"
#import "CTVSystemFeedback.h"
#import "CTV.h"

@implementation CTVRateMediaController


- (id) initWithScene: (BRRenderScene *) scene andClip:(CTVClip*)clip{
    if( [super initWithScene: scene] == nil ){
        return ( nil );
	}
	
	m_clip = clip;
	[m_clip retain];
	
	
	//Menu
	m_menuElements = [[NSMutableArray alloc] init];
	
	CTVRateMenuElement* element;
	
	element = [[CTVRateMenuElement alloc] init];
	[element setRate:-1.0f];
	[element setFunction:@selector(dontRate:)]; 
	[element setTitle:@"Don't Rate now"];
	[m_menuElements addObject:element];


	element = [[CTVRateMenuElement alloc] init];
	[element setRate:5.0f];
	[element setFunction:@selector(rateIt:)]; 
	[m_menuElements addObject:element];

	element = [[CTVRateMenuElement alloc] init];
	[element setRate:4.0f];
	[element setFunction:@selector(rateIt:)]; 
	[m_menuElements addObject:element];
	
	element = [[CTVRateMenuElement alloc] init];
	[element setRate:3.0f];
	[element setFunction:@selector(rateIt:)]; 
	[m_menuElements addObject:element];

	element = [[CTVRateMenuElement alloc] init];
	[element setRate:2.0f];
	[element setFunction:@selector(rateIt:)]; 
	[m_menuElements addObject:element];

	element = [[CTVRateMenuElement alloc] init];
	[element setRate:1.0f];
	[element setFunction:@selector(rateIt:)]; 
	[m_menuElements addObject:element];

	
	[[self list] setDatasource:self];
	
	BRAdornedMenuItemLayer* tmpresult = [BRAdornedMenuItemLayer adornedMenuItemWithScene: [self scene]];
	m_menuheight = [tmpresult defaultRowHeight] * 6;
	
	//Title + Icon
	[self setListTitle: @"Rate this video"];	
	
	NSString* iconPath =  [[NSBundle bundleForClass: [self class]] pathForResource:@"rating" ofType: @"png"];
	BRTexture * tex = [CTVCache createBitmapTextureFromPath:iconPath withScene:[self scene]];	
	[self setListIcon:tex];
	
	//Image Left
	m_image = [[BRImageControl alloc] initWithScene: [self scene]];
	if([m_clip thumbTexture] == nil){
		[m_clip loadBitmapTextureForScene:[self scene]];
	}	
	[m_image setReflectionAmount: 0.50f];
    [m_image setReflectionOffset: 0.00f];
	[m_image setTexture:[m_clip thumbTexture]];
	[self addControl:m_image];
	
	
	[self _layout];	
				
	return self;
}


- (void) dealloc{
	NSEnumerator* en = [m_menuElements objectEnumerator];
	CTVRateMenuElement* thisElement;
	while(thisElement = [en nextObject]){
		[thisElement release];
	} 
	[m_menuElements release];

	[m_clip release];
	[m_image release];
	
	[super dealloc];
}


- (long) itemCount{
	return [m_menuElements count];
}


- (id<BRMenuItemLayer>) itemForRow: (long) row{
	if ( row >= [m_menuElements count] )
		return ( nil );

	id result;
	
	CTVRateMenuElement* menuElement = [m_menuElements objectAtIndex:row];
	result = [BRAdornedMenuItemLayer adornedMenuItemWithScene: [self scene]];
	
	if([menuElement rate] == -1.0f){
		BRTexture* returnIcon = [[BRThemeInfo sharedTheme] returnToImageForScene:[self scene]];
	
		[[result textItem] setTitle:[menuElement title] withAttributes:[[BRThemeInfo sharedTheme] centeredMenuItemTextAttributes] ];
		[result setLeftIcon:returnIcon];
		
	}else{
		BRBitmapTexture* rateIcon = [CTVCache getBigRateTextureForScene:[self scene] andRate:[menuElement rate]];
		if(rateIcon){
			[result setLeftIcon:rateIcon]; 
		}
	}

	return result;
}



- (NSString *) titleForRow: (long) row{
    if ( row >= [m_menuElements count] )
		return ( nil );
		
	CTVRateMenuElement* menuElement = [m_menuElements objectAtIndex: row];
	
	return ( [menuElement title] );
}


- (long) rowForTitle: (NSString *) title{
    long result = -1;
    long i, count = [self itemCount];
    for ( i = 0; i < count; i++ )
    {
        if ( [title isEqualToString: [self titleForRow: i]] )
        {
            result = i;
            break;
        }
    }
    
    return ( result );
}

- (void) itemSelected: (long) row{
    if ( row >= [m_menuElements count] )
		return;

	// This is called when the user presses play/pause on a list item
	CTVRateMenuElement* menuElement = [m_menuElements objectAtIndex: row];


	if([menuElement function]){
		[self performSelector:[menuElement function] withObject:menuElement];
	}
	
}


- (id<BRMediaPreviewController>) previewControllerForItem: (long) item{
	return nil;
}


- (id)layer{
	return _master;
}



-(void)_layout{
	NSRect masterFrame = [[self masterLayer] frame] ;
	
	//Bitmap 
	
	
	//Menu List
	NSRect mf = NSZeroRect;
	mf.size.width = masterFrame.size.width * 0.35f;
	mf.size.height = m_menuheight * 1.30f; //masterFrame.size.height /* * 0.50f */;
	mf.origin.x = (masterFrame.size.width * 0.50f);
	mf.origin.y = (masterFrame.size.height - mf.size.height) * 0.5f;
	mf.origin.x = (((masterFrame.size.width * 0.5f) - mf.size.width) * 0.5f) + (masterFrame.size.width * 0.5f);
	mf.origin.y = (masterFrame.size.height - mf.size.height) * 0.5f;

	[[self list] setFrame:mf];

	//Image (keep aspect ratio)
    NSRect frame = masterFrame;    	
	frame.size = [m_image pixelBounds];
	//Resize frame to 40% of the height or width (biggest size counts)
	if(frame.size.width > frame.size.height){
		//Width is biggest, use 70% of the available width space (keep aspect ratio)
		float oriWidth = frame.size.width;
		float availableWidth = masterFrame.size.width * 0.5f;
		frame.size.width = availableWidth * 0.80f;
		//Aspect ratio
		float pc = frame.size.width/oriWidth;	
		frame.size.height = frame.size.height * pc;
	}else{
		//Height is biggest, use 40% of the available height space (keep aspect ratio)
		float oriHeight = frame.size.height;
		float availableHeight = masterFrame.size.height - masterFrame.origin.y;
		frame.size.height = availableHeight * 0.45f;
		//Aspect ratio
		float pc = frame.size.height/oriHeight;	
		frame.size.width = frame.size.width * pc;
	}
   
	frame.origin.x = ((masterFrame.size.width * 0.5f) - frame.size.width) * 0.5f;
	frame.origin.y = (masterFrame.size.height - frame.size.height) * 0.5f;

	[m_image setFrame:frame];
	
	
	
	
}

-(void)rateIt:(CTVRateMenuElement*)menuElement{

	int rate = (int)[menuElement rate];
	[CTVSystemFeedback rateClip:m_clip rate:rate];

	
	//Calculate the new rating local, this prevents an extra server request
	float newrate;
		
	if([m_clip viewerRate] == 0.0f){	
		if([m_clip rateCount] == 0){
			newrate = rate; 
		}else{			
			newrate = (([m_clip rate] * [m_clip rateCount]) + rate) / ([m_clip rateCount] + 1); 
		}
		[m_clip setRateCount:[m_clip rateCount] + 1];
	}else{
		if([m_clip rateCount] == 1){
			newrate = rate; 
		}else{
			float oldrate = (([m_clip rate] * [m_clip rateCount]) - [m_clip viewerRate])  / ([m_clip rateCount] - 1); 
			newrate = ((oldrate * ([m_clip rateCount] - 1)) + rate) / [m_clip rateCount] ; 
		}
	}
	
	//Round it
	newrate = roundf(newrate);
	
	[m_clip setRate:newrate];
	[m_clip setViewerRate:rate];

	//Search the clip in all channels. After a sync, the old clip-objects are replace by new ones, 
	//The m_clip reference can point to such an old object and it make no sence to write a 
	//rating to an old clip object because it will be deallocated when we leave the rate-screen

	//RootChannels
	NSEnumerator* rootChannelEnum = [[[CTV GetInstance] rootChannels] objectEnumerator];
	CTVRootChannel* rootChannel;
	while(rootChannel = [rootChannelEnum nextObject]){
		//Channels
		NSEnumerator* channelEnum = [[rootChannel channels] objectEnumerator];
		CTVChannel* channel;
		while(channel = [channelEnum nextObject]){
			//Clips
			NSEnumerator* clipEnum = [[channel clips] objectEnumerator] ;
			CTVClip* clip;
			while(clip = [clipEnum nextObject]){
				if( [[clip getUrl] isEqualToString:[m_clip getUrl]] ){
					//Set new rate
					[clip setRate:newrate];
				}
			}
		}
	}
	
	[[self stack] removeController:self];
}


-(void)dontRate:(CTVRateMenuElement*)menuElement{
	[[self stack] removeController:self];
}



- (id)popAnimation{
	id animation = [super popAnimation];
	return animation;
}


- (id)pushAnimation{
	id animation = [super pushAnimation];
	return animation;
}


- (void)activate{
	
}

- (void)willLoseFocus{

}

- (void)willRegainFocus{

}

- (void)willDeactivate{

}

- (void)deactivate{

}

- (BOOL)fadeLayerIn{
	return TRUE;
}

- (void)setDeletterboxAssetArtwork:(BOOL)fp8{

}

@end







/***********************
 * CTVRateMenuElement
 */
@implementation CTVRateMenuElement

-(id)init{
	self = [super init];
	return self;
}

-(void)dealloc{
	if(m_title){
		[m_title release];
	}
	[super dealloc];
}

-(NSString*)title{
	return m_title;
}

-(float)rate{
	return m_rate;
}
-(void)setTitle:(NSString*)title{
	if(m_title){
		[m_title release];
	}
	[title retain];
	m_title = title;
}

-(void)setRate:(float)rate{
	m_rate = rate;
}

-(void)setFunction:(SEL)function{
	m_function = function;
}

-(SEL)function{
	return m_function;
}


@end
